package com.joshua.spring.configuration;

import com.joshua.spring.integration.IntegrationUserDetailServiceImpl;
import com.joshua.spring.property.Oauth2Properties;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableResourceServer;

/**
 * com.joshua.spring.business.configuration -- WebSecurityConfiguration
 * description: spring security配置
 * 先构建HttpSecurity对象，然后通过
 * {@link WebSecurity#addSecurityFilterChainBuilder}
 * 添加到securityFilterChainBuilders的List中，最后用来组件过滤器链。
 *
 * @author <a href="mailto:joshualwork@163.com">joshua_liu</a>
 * @date 2020/1/2 15:40
 */
@Configuration
@EnableWebSecurity
@EnableResourceServer
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true, jsr250Enabled = true)
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Autowired
    private Oauth2Properties oauth2Properties;
    @Autowired
    private IntegrationUserDetailServiceImpl userDetailService;

    /**
     * description: AuthenticationManagerBuilder用来配置全局的认证相关的信息，
     * 其实就是AuthenticationProvider(认证服务提供者)
     * 和UserDetailsService(认证用户及其权限)
     *
     * @param auth
     * @author <a href="mailto:joshualwork@163.com">joshua_liu</a>
     * @date 2020/1/2 16:55
     */
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userDetailService);
    }

    /**
     * description:HttpSecurity 具体的权限控制规则配置。一个配置相当于xml
     * 配置中的一个标签。各种具体的认证机制的相关配置，
     * 当前配置为将授权访问配置改为注解方式
     *
     * @param http
     * @author <a href="mailto:joshualwork@163.com">joshua_liu</a>
     * @date 2020/1/2 16:55
     */
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.exceptionHandling()
                .and().sessionManagement()
                .sessionCreationPolicy(SessionCreationPolicy.STATELESS);
    }

    /**
     * description:WebSecurity 全局请求忽略规则配置（比如说静态文件，比如说注册页面）,
     * 全局HttpFirewall配置、是否debug配置、全局SecurityFilterChain配置、privilegeEvaluator、
     * expressionHandler、securityInterceptor。
     *
     * @param web
     * @author <a href="mailto:joshualwork@163.com">joshua_liu</a>
     * @date 2020/1/2 16:55
     */
    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers(oauth2Properties.getIgnoreUris());
    }

    /**
     * description: {@link AuthorizationServerConfiguration}
     *
     * @return {@link AuthenticationManager}
     * @author <a href="mailto:joshualwork@163.com">joshua_liu</a>
     * @date 2020/1/2 16:55
     */
    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }
}
